import { MinOrDayData } from "@/assets/api/rtdatasubscriberservice_0_0_1";

const upColor = "#c12328";
const downColor = "#199319";
// const downColor = 'blue';
const axisLineColor = "#999999";
const axisLabelColor = "#666666";
const splitLineColor = "#eee";

const SYMBOL = Object.freeze({
  LEFT: `path://M441.284937 133.491317l24.940019 25.712615c5.762237 5.962805 8.940626 13.833053 8.940626 22.179139 
0 8.384971-3.178389 16.256242-8.940626 22.177092L212.794989 464.957591l726.44507 0c10.968819 0 19.911492 8.903787 
19.911492 19.832697l0 51.627844c0 10.968819-8.942673 19.871583-19.911492 19.871583L212.595444 556.289716l253.628488 
261.558088c5.762237 5.921873 8.940626 13.831007 8.940626 22.177092 0 8.385994-3.178389 16.256242-8.940626 
22.177092l-24.940019 25.714661c-5.882987 6.080485-13.731746 9.419534-22.098297 9.419534-8.385994 0-16.256242-3.339048-22.157649-9.419534L72.655252 
553.388643c-0.3776-0.398066-0.715291-0.794086-1.01205-1.153266-4.869914-3.696182-7.849782-9.458419-7.849782-15.818267l0-51.626821c0-6.477528 
3.098571-12.360516 8.18645-16.016789 0.23843-0.277316 0.476861-0.556679 0.7552-0.836041l324.313364-334.445118c5.881964-6.081509 
13.751189-9.420557 22.138206-9.420557C427.553191 124.07076 435.401949 127.45074 441.284937 133.491317z`,
  RIGHT: `path://M581.661058 887.916649l-24.940019-25.712615c-5.762237-5.962805-8.940626-13.833053-8.940626-22.179139 0-8.384971 
3.178389-16.256242 8.940626-22.177092l253.429966-261.397429-726.44507 0c-10.968819 0-19.911492-8.903787-19.911492-19.832697l0-51.627844c0-10.968819 
8.942673-19.871583 19.911492-19.871583l726.644615 0L556.721039 203.560162c-5.762237-5.921873-8.940626-13.831007-8.940626-22.177092 
0-8.385994 3.178389-16.256242 8.940626-22.177092l24.940019-25.714661c5.882987-6.080485 13.731746-9.419534 22.098297-9.419534 
8.385994 0 16.256242 3.339048 22.157649 9.419534l324.372715 334.526983c0.3776 0.398066 0.715291 0.795109 1.01205 1.153266 4.869914 
3.696182 7.849782 9.459442 7.849782 15.818267l0 51.627844c0 6.477528-3.098571 12.360516-8.18645 16.016789-0.23843 0.277316-0.476861 0.556679-0.7552 
0.836041L625.897561 887.916649c-5.881964 6.081509-13.751189 9.420557-22.138206 9.420557C595.392804 897.337205 587.544045 893.957225 581.661058 887.916649z`,
  UP: "path://M273.6 593l212.9-212.9c14.1-14.1 36.9-14.1 50.9 0l213 212.9c22.7 22.7 6.6 61.5-25.5 61.5H299.1c-32.1 0-48.1-38.8-25.5-61.5z",
  DOWN: "path://M273.6 431l212.9 212.9c14.1 14.1 36.9 14.1 50.9 0l213-212.9c22.7-22.7 6.6-61.5-25.5-61.5H299.1c-32.1 0-48.1 38.8-25.5 61.5z",
});

export const lineTypes = {
  KLINE: 0, // 正常k线
  SAMPLE_LINE: 1, // 采样线
};

const baseOption = {
  animation: false,
  axisPointer: {
    link: { xAxisIndex: "all" },
    label: {
      backgroundColor: "#454545",
    },
  },
};

const tooltipsCommon = {
  trigger: "axis",
  axisPointer: {
    type: "cross",
  },
  backgroundColor: "rgba(255, 255, 255, 0.85)",
  borderWidth: 1,
  borderColor: "#ccc",
  padding: 10,
  textStyle: {
    color: "#444",
  },
  confine: true,
  hideDelay: 5000,
};

const xAxissCommon = {
  type: "category",
  axisLabel: {
    color: axisLabelColor,
  },
  axisLine: {
    lineStyle: {
      color: axisLineColor,
    },
  },
  min: "dataMin",
  max: "dataMax",
};

const xAxiss = [
  // k线
  {
    ...xAxissCommon,
    data: [],
    axisPointer: {
      z: 100,
    },
  },
  // 交易量bar
  {
    type: "category",
    gridIndex: 1,
    data: [],
    axisLine: {
      onZero: false,
      lineStyle: {
        color: axisLineColor,
      },
    },
    axisTick: { show: false },
    splitLine: { show: false },
    axisLabel: { show: false },
    min: "dataMin",
    max: "dataMax",
  },
  // k线（采样）
  {
    ...xAxissCommon,
    data: [],
  },
  // 分时图
  {
    ...xAxissCommon,
    data: [],
  },
];

const yAxissCommon = {
  type: "value",
  scale: true,
  axisLabel: {
    color: axisLabelColor,
    fontSize: 11,
  },
  axisLine: {
    lineStyle: {
      color: axisLineColor,
    },
  },
  splitLine: {
    show: true,
    lineStyle: {
      color: splitLineColor,
      type: "dashed",
    },
  },
};

const yAxiss: any = [
  // k线
  {
    ...yAxissCommon,
  },
  // 交易量bar
  {
    min: "0",
    // scale: true,
    gridIndex: 1,
    // splitNumber: 2,
    ...yAxissCommon,
    axisLabel: {
      fontSize: 10,
      formatter: (value /* , index */) => {
        value = Number(value);
        if (value >= 10000 && value < 100000000) {
          return Number((value / 10000).toFixed(2)) + "万";
        } else if (value >= 100000000) {
          return Number((value / 100000000).toFixed(2)) + "亿";
        } else return value;
      },
    },
  },
  // k线（采样）
  {
    ...yAxissCommon,
  },
  // 分时图
  {
    ...yAxissCommon,
  },
];
const commonMarkPoint = {
  label: {
    color: "#565656",
    offset: [30, 0],
  },
  itemStyle: {
    color: "#565656",
  },
  symbol: SYMBOL.LEFT,
  symbolOffset: [7, -2],
  symbolSize: 12,
  animation: false,
};
const series = [
  {
    name: "K线图",
    type: "k",
    itemStyle: {
      normal: {
        color: downColor,
        borderColor: downColor,
        borderWidth: 0.5,
        color0: "#ffffff",
        borderColor0: upColor,
        borderWidth0: 0.5,
      },
    },
    barMinWidth: 5,
    barMaxWidth: 50,
    hoverAnimation: false,
    markPoint: {
      ...commonMarkPoint,
      data: [],
    },
    data: [],
  },
  {
    name: "手数",
    type: "bar",
    xAxisIndex: 1,
    yAxisIndex: 1,
    barMinWidth: 5,
    barMaxWidth: 50,
    barCategoryGap: "40%",
    data: [],
  },
  // 采样线
  {
    type: "line",
    data: [],
    smooth: true,
    showSymbol: false,
    lineStyle: {
      width: 1,
      color: "#ff6600",
    },
    markPoint: {
      ...commonMarkPoint,
      data: [],
    },
  },
];
// 控制两个表格的宽度何距离
const grids = [
  {
    left: 60,
    right: 20,
    top: 20,
    height: '50%',
  },
  {
    left: 60, // 
    right: 20,
    top: '54%',
    bottom: 20,
  },
];

// 找出k线的最高最低
function getKlineMinMaxMarkpointData(
  kdatas: Array<MinOrDayData>,
  type = lineTypes.KLINE
) {
  if (!kdatas || !kdatas.length) return [];
  const max = {
    value: 0,
    index: 0,
    x: "0",
    y: 0,
    nearRight: false,
  };
  const min = {
    value: Number.MAX_SAFE_INTEGER,
    index: 0,
    x: "0",
    y: 0,
    nearRight: false,
  };
  const len = kdatas.length;
  for (const [index, item] of kdatas.entries()) {
    if (type === lineTypes.KLINE) {
      if (item.low < min.value) {
        min.index = index;
        min.value = Number(item.low);
      }
      if (item.high > max.value) {
        max.index = index;
        max.value = Number(item.high);
      }
    } else if (type === lineTypes.SAMPLE_LINE) {
      if (item.close < min.value) {
        min.index = index;
        min.value = Number(item.close);
      }
      if (item.close > max.value) {
        max.index = index;
        max.value = Number(item.close);
      }
    }
  }

  let min_datetime = kdatas[min.index].datetime.toString();
  // 提取月份和日期
  const min_year = min_datetime.substring(0, 4);
  const min_month = min_datetime.substring(4, 6);
  const min_day = min_datetime.substring(6, 8);
  const min_hour = min_datetime.substring(8, 10);
  const min_minute = min_datetime.substring(10, 12);

  min.x = `${min_year}-${min_month}-${min_day} ${min_hour}:${min_minute}`; //dayjs(rawData[min.index].ptTime).format(dateFormat);

  min.y = min.value;
  min.nearRight = min.index >= len - 5;

  let max_datetime = kdatas[max.index].datetime.toString();
  // 提取月份和日期
  const max_year = max_datetime.substring(0, 4);
  const max_month = max_datetime.substring(4, 6);
  const max_day = max_datetime.substring(6, 8);
  const max_hour = max_datetime.substring(8, 10);
  const max_minute = max_datetime.substring(10, 12);

  max.x = `${max_year}-${max_month}-${max_day} ${max_hour}:${max_minute}`;
  max.y = max.value;
  max.nearRight = max.index >= len - 5;
  return [
    {
      name: "最大值",
      symbol: max.nearRight ? SYMBOL.RIGHT : SYMBOL.LEFT,
      symbolOffset: [max.nearRight ? -8 : 8, 0],
      label: {
        offset: [max.nearRight ? -30 : 30, 0],
      },
      value: max.value,
      coord: [max.x, max.y],
    },
    {
      name: "最小值",
      symbol: min.nearRight ? SYMBOL.RIGHT : SYMBOL.LEFT,
      symbolOffset: [min.nearRight ? -8 : 8, 0],
      label: {
        offset: [min.nearRight ? -30 : 30, 0],
      },
      value: min.value,
      coord: [min.x, min.y],
    },
  ];
}
//计算交易量bar的数据项
// 有交易数据的
// 底部的柱状图
function getVolumnSerieData(kdatas: Array<MinOrDayData>) {
  return kdatas.map((item, index) => {
    // fix(#6125), string 类型比较大小bug
    const isUp = item.close - item.open > 0;
    return {
      value: [index, item.volume, isUp ? 1 : -1],
      itemStyle: {
        normal: isUp
          ? {
            color: "#ffffff",
            borderColor: upColor,
            // eslint-disable-next-line eqeqeq
            borderWidth: item.volume == 0 ? 0 : 0.5,
          }
          : {
            color: downColor,
            borderColor: downColor,
            // eslint-disable-next-line eqeqeq
            borderWidth: item.volume == 0 ? 0 : 0.5,
          },
      },
    };
  });
}

//  分钟线
export default function (
  kdatas: Array<MinOrDayData>,
  type: string,
  freqType: string
) {
  // 正常的k线图
  if (type === "normal") {
    // 分时图
    if (freqType === "tick") {
      // 10-21 15:00
      const dates = kdatas.map((item) => {
        let datetime = item.datetime.toString();
        // 提取月份和日期
        const month = datetime.substring(4, 6);
        const day = datetime.substring(6, 8);
        const hour = datetime.substring(8, 10);
        const minute = datetime.substring(10, 12);
        return `${month}-${day} ${hour}:${minute}`;
      });

      let option = {
        ...baseOption,
        tooltip: {
          ...tooltipsCommon,
          formatter: (params) => {
            const whiteLine = params[0];
            const yellowLine = params[1];
            const volumn = params[2];
            return `时间：${whiteLine.axisValue} <br />
           成交： ${whiteLine.data}  <br />
           均价： ${yellowLine.data}  <br />
           分时量： ${volumn.data}<br />`;
          },
        },
        grid: [grids[0], grids[1]],
        xAxis: [xAxiss[3], xAxiss[1]],
        yAxis: [yAxiss[3], yAxiss[1]],
        series: [
          {
            name: "白线",
            type: "line",
            smooth: true,
            showSymbol: false,
            lineStyle: {
              width: 1,
              color: "#696969",
            },
            data: kdatas.map((item) => item.close),
          },
          {
            name: "黄线",
            type: "line",
            smooth: true,
            showSymbol: false,
            lineStyle: {
              width: 1,
              color: "#faad14",
            },
            data: kdatas.map((item) => item.average),
          },
          series[1],
        ],
      };

      option.xAxis[0].data = dates;
      option.xAxis[1].data = dates;

      option.series[2].data = kdatas.map((item) => {
        return item.volume;
      });
      return option;
    } else {
      let option = {
        ...baseOption,
        tooltip: {
          ...tooltipsCommon,
          formatter: (params) => {
            let kline = params[0];
            let volumn = params[1];
            if (params[0].seriesIndex != 0) {
              kline = params[1];
              volumn = params[0];
            }

            return `时间：${kline.axisValue} <br/>
              收盘：${kline.data.value[1]} <br/>
              开盘：${kline.data.value[2]} <br/> 
              最低：${kline.data.value[3]} <br/>
              最高：${kline.data.value[4]} <br/> 
              成交额：${kline.data.value[5]} <br />
              交易量： ${volumn.data.value[1]} <br />
              涨跌： 0 <br/>
              涨跌幅： 0 % <br/>`;

          },
        },
        grid: [grids[0], grids[1]],
        xAxis: [xAxiss[0], xAxiss[1]],
        yAxis: [yAxiss[0], yAxiss[1]],
        series: [series[0], series[1]],
      };
      // 2024-10-21 15:00
      const dates = kdatas.map((item) => {
        let datetime = item.datetime.toString();
        // 提取月份和日期
        const year = datetime.substring(0, 4);
        const month = datetime.substring(4, 6);
        const day = datetime.substring(6, 8);
        const hour = datetime.substring(8, 10);
        const minute = datetime.substring(10, 12);
        return `${year}-${month}-${day} ${hour}:${minute}`;
      }) as any;
      option.xAxis[0].data = dates;

      option.series[0].data = kdatas.map((item) => {
        const isEven = item.close === item.open;
        const bar = {
          value: [
            item.close,
            item.open,
            item.low,
            item.high,
            item.total_turnover,
            "0",
            "0",
          ],
          itemStyle: {},
        };
        if (isEven) {
          bar.itemStyle = {
            color: "#454545",
            borderColor: "#454545",
            borderWidth: 0.5,
            color0: "#454545",
            border0Width: 0.5,
            borderColor0: "#454545",
          };
        }
        return bar;
      }) as any;

      //获取K线的最大值和最小值
      option.series[0].markPoint.data = getKlineMinMaxMarkpointData(
        kdatas
      ) as any;
      option.xAxis[1].data = dates;
      option.series[1].data = getVolumnSerieData(kdatas) as any;
      // #2536
      option.yAxis[0] = {
        ...option.yAxis[0],
        max: (value) => {
          const topValue = value.max + (value.max - value.min) * 0.12;
          return (Math.ceil(topValue * 1000) / 1000).toFixed(3);
        },
        min: (value) => {
          const downValue = value.min - (value.max - value.min) * 0.12;
          return (Math.floor(downValue * 1000) / 1000).toFixed(3);
        },
      };
      return option;
    }
  } else if (type === "sample") {
  } else {
    return { ...baseOption };
  }
}
